package cgl.narada.service.security.kmc.messages;

import java.io.IOException;
import java.io.Serializable;
import java.security.cert.Certificate;
import java.util.Calendar;
import java.util.Hashtable;

import org.apache.log4j.Logger;

import cgl.narada.discovery.topics.messages.SignedTopicAdvertisement;
import cgl.narada.util.ObjectMarshaller;

public class SecureTopicKeyCreateUpdateRequest implements Serializable {

    static Logger log = Logger.getLogger("SecureTopicKeyCreateUpdateRequest");

    /** Signed Topic Advertisement for which a security key is to be created */
    private SignedTopicAdvertisement topicAd;

    /** Owner's credentials */
    private Certificate ownerCredentials;

    // HG: Modifications for NB Security
    // NOTES:
    // * Usually a topic owner should specifiy DN of entities who are allowed to
    // publish or subscribe
    // * By default the value is '*' => ANYBODY allowed !!

    /** Publisher access list */
    private Hashtable allowedPublishers;

    /** Subscriber access list */
    private Hashtable allowedSubscribers;

    /** How long should subsequent tokens be valid ? */
    private Calendar validity;

    /** Response Topic */
    private String responseTopic;

    /* Secure Token Generation parameters */

    /** SecretKey generation algorithm */
    private String algorithm;   
    
    /** SecretKey keySize in bits */
    private int keySize;   

    /**
     * Create a Secure Topic key creation request. To be used by the topic owner
     * 
     * @param pubs -
     *            A vector of allowed publishers to this topic
     * @param subs -
     *            A vector of allowed subscribers to this topic
     * @param sta -
     *            The signed topic advertisement
     * @param creds -
     *            The owner's certificate (X.509). This will be used to validate
     *            the topic ad's signature
     */
    public SecureTopicKeyCreateUpdateRequest(Hashtable pubs, Hashtable subs,
            SignedTopicAdvertisement sta, Certificate creds,
            Calendar validUntil, String alg, int _keySize, String response) {
        allowedPublishers = new Hashtable();
        allowedSubscribers = new Hashtable();

        if (pubs == null)
            allowedPublishers.put("*", "*");
        else 
            allowedPublishers = pubs;

        if (subs == null)
            allowedSubscribers.put("*", "*");
        else
            allowedSubscribers = subs;

        topicAd = sta;
        ownerCredentials = creds;
        validity = validUntil;
        responseTopic = response;

        // default values are
        algorithm = alg;
        keySize = _keySize;
    }

    /**
     * Marshalls the object into an array of bytes.
     * 
     * @return an array of bytes representing the marshaller object, null if
     *         error occurs
     */
    public byte[] getBytes() {
        try {
            return ObjectMarshaller.marshall(this);
        } catch (IOException e) {
            log.error("", e);
            return null;
        }
    }

    /**
     * Unmarshalls the bytes as a SecureTopicKeyCreateUpdateRequest object
     * 
     * @param objectBytes
     * @return SecureTopicKeyCreateUpdateRequest if successful, null if error
     *         occurs
     */
    public static SecureTopicKeyCreateUpdateRequest createObjectFromBytes(
            byte[] objectBytes) {
        try {
            return (SecureTopicKeyCreateUpdateRequest) ObjectMarshaller
                    .unmarshall(objectBytes);
        } catch (IOException e) {
            log.error("", e);
        } catch (ClassNotFoundException e) {
            log.error("", e);
        }
        return null;
    }

    /**
     * @return Returns the allowedPublishers.
     */
    public Hashtable getAllowedPublishers() {
        return allowedPublishers;
    }

    /**
     * @return Returns the allowedSubscribers.
     */
    public Hashtable getAllowedSubscribers() {
        return allowedSubscribers;
    }

    /**
     * @return Returns the ownerCredentials.
     */
    public Certificate getOwnerCredentials() {
        return ownerCredentials;
    }

    /**
     * @return Returns the responseTopic.
     */
    public String getResponseTopic() {
        return responseTopic;
    }

    /**
     * @return Returns the topicAd.
     */
    public SignedTopicAdvertisement getTopicAd() {
        return topicAd;
    }

    /**
     * @return Returns the validity.
     */
    public Calendar getValidity() {
        return validity;
    }

    /**
     * @return Returns the algorithm.
     */
    public String getAlgorithm() {
        return algorithm;
    }

    /**
     * @return Returns the keySize.
     */
    public int getKeySize() {
        return keySize;
    }
}
